package leetcode;

import org.junit.Before;
import org.junit.Test;

import java.util.*;

/*
    给定一个字符串 s ，请你找出其中不含有重复字符的 最长 子串 的长度。
        示例 1:
        输入: s = "abcabcbb"
        输出: 3
        解释: 因为无重复字符的最长子串是 "abc"，所以其长度为 3。注意 "bca" 和 "cab" 也是正确答案。

        示例 2:
        输入: s = "bbbbb"
        输出: 1
        解释: 因为无重复字符的最长子串是 "b"，所以其长度为 1。

        示例 3:
        输入: s = "pwwkew"
        输出: 3
        解释: 因为无重复字符的最长子串是 "wke"，所以其长度为 3。
        请注意，你的答案必须是 子串 的长度，"pwke" 是一个子序列，不是子串。

        提示：
            0 <= s.length <= 5 * 104
            s 由英文字母、数字、符号和空格组成*/
public class LongestSubstringWithoutRepeatingCharacters {
    private String s;
    @Before
    public void dataInit() {
        s = "abcbbacbb";
    }

    @Test
    public void method_1() {
        // 使用固定大小的数组（ASCII字符集）记录字符最后出现的位置
        int[] lastSeen = new int[120]; // 覆盖所有ASCII字符

        for (int i = 0; i < 120; i++) {
            lastSeen[i] = -1; // 初始化所有字符为未出现的状态
        }

        int left = 0; // 滑动窗口的左边界
        int maxLen = 0; // 最长子串的长度

        for (int right = 0; right < s.length(); right++){
            char c = s.charAt(right);
            System.out.println(lastSeen[c]);
            // 如果当前字符在窗口内已出现过，移动左边界到重复字符的下一个位置
            if (lastSeen[c] >= left){
                left = lastSeen[c] + 1;
            }

            lastSeen[c] = right;
            maxLen = Math.max(maxLen, right - left + 1);
        }
        System.out.println(maxLen);
    }
}
